package com.witmore.neutron.ai.web.config;

import com.witmore.neutron.ai.web.apiv2.filter.ApiTokenAuthenticationInterceptor;
import com.witmore.neutron.ai.web.filter.AccessTokenAuthenticationFilter;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.format.Formatter;
import org.springframework.format.FormatterRegistry;
import org.springframework.scheduling.concurrent.ThreadPoolTaskExecutor;
import org.springframework.web.servlet.ViewResolver;
import org.springframework.web.servlet.config.annotation.AsyncSupportConfigurer;
import org.springframework.web.servlet.config.annotation.InterceptorRegistry;
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
import org.thymeleaf.spring6.SpringTemplateEngine;
import org.thymeleaf.spring6.view.ThymeleafViewResolver;

import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.time.format.DateTimeParseException;
import java.util.Locale;

@Configuration
public class WebConfig implements WebMvcConfigurer {

    @Autowired
    private ApiTokenAuthenticationInterceptor apiTokenFilter;

    @Autowired
    private AccessTokenAuthenticationFilter accessTokenFilter;

    private final ThreadPoolTaskExecutor mvcTaskExecutor;

    public WebConfig(ThreadPoolTaskExecutor mvcTaskExecutor) {
        this.mvcTaskExecutor = mvcTaskExecutor;
    }


    /**
     * MVC异步执行器配置：
     *
     * @Async 注解 和 Spring MVC 的异步请求使用不同的执行器
     * 项目中自定义的线程池ThreadPoolConfig 只用于@Async 注解的方法，而MVC异步请求需要单独配置，否则会有个警告⚠️如下：
     * <p>
     * 2025-06-30 10:22:59 [reactor-http-nio-3] WARN  o.s.w.s.m.m.a.RequestMappingHandlerAdapter - !!!
     * Performing asynchronous handling through the default Spring MVC SimpleAsyncTaskExecutor.
     * This executor is not suitable for production use under load.
     * Please, configure an AsyncTaskExecutor through the WebMvc config.
     * -------------------------------
     * !!!
     */
    @Override
    public void configureAsyncSupport(AsyncSupportConfigurer configurer) {
        configurer.setTaskExecutor(mvcTaskExecutor);
    }

    @Bean
    public ViewResolver thymeleafViewResolver(SpringTemplateEngine templateEngine) {
        ThymeleafViewResolver resolver = new ThymeleafViewResolver();
        resolver.setTemplateEngine(templateEngine);
        resolver.setCharacterEncoding("UTF-8");
        return resolver;
    }

    @Override
    public void addFormatters(FormatterRegistry registry) {
        registry.addFormatterForFieldType(LocalDateTime.class, new Formatter<LocalDateTime>() {
            @Override
            public String print(LocalDateTime object, Locale locale) {
                return object.format(DateTimeFormatter.ofPattern("yyyy年MM月dd日"));
            }

            @Override
            public LocalDateTime parse(String text, Locale locale) {
                if (text == null || text.trim().isEmpty()) {
                    throw new IllegalArgumentException("日期时间字符串不能为空");
                }
                
                text = text.trim(); // 去除前后空格
                
                // 支持多种日期时间格式
                try {
                    // 首先尝试 yyyy-MM-dd HH:mm:ss 格式 (URL参数常用格式)
                    return LocalDateTime.parse(text, DateTimeFormatter.ofPattern("yyyy-MM-dd HH:mm:ss"));
                } catch (DateTimeParseException e1) {
                    try {
                        // 然后尝试 ISO 格式 (JSON常用格式)
                        return LocalDateTime.parse(text, DateTimeFormatter.ISO_LOCAL_DATE_TIME);
                    } catch (DateTimeParseException e2) {
                        try {
                            // 尝试只有日期的格式，时间设为00:00:00
                            return LocalDateTime.parse(text + "T00:00:00", DateTimeFormatter.ISO_LOCAL_DATE_TIME);
                        } catch (DateTimeParseException e3) {
                            // 如果都失败了，抛出详细的错误信息
                            throw new IllegalArgumentException(
                                String.format("无法解析日期时间字符串: '%s'。支持的格式: 'yyyy-MM-dd HH:mm:ss' 或 ISO格式", text), e3);
                        }
                    }
                }
            }
        });
    }

    @Override
    public void addInterceptors(InterceptorRegistry registry) {
        // 配置第一个拦截器 (ApiTokenAuthenticationInterceptor)
        registry.addInterceptor(apiTokenFilter)
                .order(0) // 设置执行顺序（数字越小优先级越高）
                .addPathPatterns("/**")
                .excludePathPatterns(ApiTokenAuthenticationInterceptor.EXCLUDE_URLS);

        // 配置第二个拦截器 (AccessTokenAuthenticationFilter)
        registry.addInterceptor(accessTokenFilter)
                .order(1)
                .excludePathPatterns(AccessTokenAuthenticationFilter.EXCLUDE_URLS)
                .addPathPatterns("/**");
    }


}
